package com.bestcem.xm.txtanls.util;

import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.ExcelReader;
import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.event.AnalysisEventListener;
import com.alibaba.excel.read.metadata.ReadSheet;
import com.bestcem.xm.txtanls.service.dto.train.DemoDataDTO;
import com.bestcem.xm.txtanls.service.dto.train.FreeDataDTO;
import lombok.extern.slf4j.Slf4j;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.core.io.ClassPathResource;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;

import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.List;

/**
 * @author XiaoYunSong <ys.xiao@idiaoyan.com>
 * @version v1.0
 * @date 2021/6/8 17:45
 */

@Slf4j
@Component
public class TestAsyncTaskUtil {
    private static List<DemoDataDTO> demoDateCache = new ArrayList<>();
    private static List<FreeDataDTO> freeDateCache = new ArrayList<>();

    public List<DemoDataDTO> readDemoDataExcel() {
        if (!CollectionUtils.isEmpty(demoDateCache)) {
            return demoDateCache;
        }
        ExcelReader excelReader = null;
        try {
            ClassPathResource resource = new ClassPathResource("/file/txtanls_demo.xlsx");
            DemoDataListener listener = new DemoDataListener();
            excelReader = EasyExcel.read(resource.getInputStream(), DemoDataDTO.class, listener).build();
            ReadSheet readSheet = EasyExcel.readSheet(0).build();
            excelReader.read(readSheet);
            return demoDateCache = listener.list;
        } catch (Exception ignored) {
            return null;
        } finally {
            if (excelReader != null) {
                // 这里千万别忘记关闭，读的时候会创建临时文件，到时磁盘会崩的
                excelReader.finish();
            }
        }
    }

    public List<FreeDataDTO> readFreeDataExcel() {
        if (!CollectionUtils.isEmpty(freeDateCache)) {
            return freeDateCache;
        }
        ExcelReader excelReader = null;
        try {
            ClassPathResource resource = new ClassPathResource("/file/free.xlsx");
            FreeDataListener listener = new FreeDataListener();
            excelReader = EasyExcel.read(resource.getInputStream(), FreeDataDTO.class, listener).build();
            ReadSheet readSheet = EasyExcel.readSheet(0).build();
            excelReader.read(readSheet);
            return freeDateCache = listener.list;
        } catch (Exception ignored) {
            log.error("文本分析初始化项目读取excel错误");
            return null;
        } finally {
            if (excelReader != null) {
                // 这里千万别忘记关闭，读的时候会创建临时文件，到时磁盘会崩的
                excelReader.finish();
            }
        }
    }

    public Object getPropertyValue(Object obj, String propertyName) throws IllegalAccessException {
        Class<?> Clazz = obj.getClass();
        Field field;
        if ((field = getField(Clazz, propertyName)) == null) {
            return null;
        }
        field.setAccessible(true);
        return field.get(obj);
    }

    public Field getField(Class<?> clazz, String propertyName) {
        if (clazz == null) {
            return null;
        }
        try {
            return clazz.getDeclaredField(propertyName);
        } catch (NoSuchFieldException e) {
            return getField(clazz.getSuperclass(), propertyName);
        }
    }

    // 有个很重要的点 DemoDataListener 不能被spring管理，要每次读取excel都要new,然后里面用到spring可以构造方法传进去
    static class DemoDataListener extends AnalysisEventListener<DemoDataDTO> {
        private static final Logger LOGGER = LoggerFactory.getLogger(DemoDataListener.class);
        List<DemoDataDTO> list = new ArrayList<>();

        @Override
        public void invoke(DemoDataDTO map, AnalysisContext analysisContext) {
            list.add(map);
        }

        @Override
        public void doAfterAllAnalysed(AnalysisContext context) {
            LOGGER.info("[Txtanls] 所有数据解析完成！" + list.size());
        }
    }

    // 有个很重要的点 DemoDataListener 不能被spring管理，要每次读取excel都要new,然后里面用到spring可以构造方法传进去
    static class FreeDataListener extends AnalysisEventListener<FreeDataDTO> {
        private static final Logger LOGGER = LoggerFactory.getLogger(FreeDataListener.class);
        List<FreeDataDTO> list = new ArrayList<>();

        @Override
        public void invoke(FreeDataDTO map, AnalysisContext analysisContext) {
            list.add(map);
        }

        @Override
        public void doAfterAllAnalysed(AnalysisContext context) {
            LOGGER.info("[Txtanls] 所有数据解析完成！" + list.size());
        }

    }
}

